/**
 *  Platypus: Page Layout and Typesetting Software (free at platypus.pz.org)
 *
 *  Platypus is (c) Copyright 2009-11 Pacific Data Works LLC. All Rights Reserved.
 *  Licensed under Apache License 2.0 (http://www.apache.org/licenses/LICENSE-2.0.html)
 */
package org.pz.platypus;

import org.apache.commons.cli.CommandLine;
import org.junit.*;
import org.pz.platypus.commandline.*;
import org.pz.platypus.exceptions.*;
import org.pz.platypus.mocks.MockLiterals;
import org.pz.platypus.utilities.PlatypusHomeDirectory;

import java.io.*;
import java.util.logging.Level;

import static org.junit.Assert.*;

/**
 * @author alb
 */
public class ConfigFileTest
{
    ClParser clp;
    GDD gdd;

    @Before
    public void setUp()
    {
        Literals lits;

        String args[] = { "" };
        PlatypusHomeDirectory homeDir = new PlatypusHomeDirectory( args );
        gdd = new GDD( homeDir.get() );

        MockLiterals mockLits = new MockLiterals( "Platypus.properties" );
        mockLits. setGetLitShouldReturnValue( true );
        lits = mockLits;
        gdd.setupGdd( lits );
        gdd.log.setLevel( Level.OFF );

        // create a mock config file

        final String configFilename = "./config.mock";
        try {
            BufferedWriter out = new BufferedWriter(new FileWriter( configFilename ));
            // create minimal entries for pdf and html plugin
            out.write( "pi.out.pdf=pdf.mock\n" );
            out.write( "pi.out.html=html.mock\n" );
            out.close();
            } catch (IOException e) {
        }

        ConfigFile cf = new ConfigFile( new ConfigLocator( configFilename ), gdd );
        gdd.configFile = cf;

        // now create a file that can appear to be the plugin

        try {
            new File("./plugin").mkdir();
            new File( "./plugin/pdf.mock" ).createNewFile();
            new File( "./plugin/html.mock" ).createNewFile();
        } catch (IOException e) {
            fail( "***ERROR OCCURRED IN ConfigFileTest.java***" );
        }
    }

    @After
    public void tearDown()
    {
        File dir = new File( "./plugin" );

         if (dir.isDirectory()) {
             File[] fs=dir.listFiles();
             for (int i=0;i<fs.length;i++) {
                fs[i].delete();
             }
         }

         if (!(dir.delete())) {
             System.err.println("cannot delete: " + dir );
         }
    }

    /**
     * Tests config file by using the mock config file to locate and validate the presence of a PDF plugin
     */
    @Test
    public void testStandardCommandLineForProperRecordingOfFormat()
    {

        String[] args = new String[] {
            "input.txt", "output.pdf", "-vverbose"
        };

        clp = new ClParser( args );
        CommandLine cli = clp.getLine();
        assertTrue( cli != null );

        try {  // regardless of whether PDF plugin is there...
            ClProcessor clproc = new ClProcessor( clp, args, gdd );
            clproc.process();
        }
        catch( StopExecutionException soe ) {}

        //...did we update the _FORMAT entry in strings table and toggle VVerbose to on?
        assertEquals( "pdf", gdd.sysStrings.get("_FORMAT"));
        assertTrue( gdd.clVVerbose );
    }

    /**
     * Tests the config file by making sure that the
     */
    @Test
    public void testNoOutfile()
    {
        boolean simulatedPlugin = false;
        File simPlugin = null;

        // create a plugin file facsimile if the plugin does not exist in the test environment
        PluginLocator locator = new PluginLocator( gdd );
        try {
            locator.locate( "pdf" );
        }
        catch ( StopExecutionException soe ) {
            byte[] content = {'a', 'l', 'b'};
            simPlugin = new File( locator.getLocation() );
            try {
                com.google.common.io.Files.write( content, simPlugin );
                System.out.println( "created simulated plugin: " + locator.getLocation() );
            }
            catch( IOException ioe ) {
                fail( "IOException in testNoOutfile() in ConfigFileTest.java" );
            }
            simulatedPlugin = true;
        }

        // now start the test
        String[] args = new String[] {
            "input.txt"
        };

        clp = new ClParser( args );
        CommandLine cli = clp.getLine();
        assertTrue( cli != null );

        ClProcessor clproc = new ClProcessor( clp, args, gdd );
        clproc.process();

        assertEquals( "pdf", gdd.sysStrings.get("_FORMAT"));
        assertEquals( "input.pdf", gdd.sysStrings.get("_OUTPUT_FILE"));

        // clean up any simulated plugin
        if( simulatedPlugin ) {
            simPlugin.delete();
        }
    }

    @Test
    public void testFormatSwitch()
    {
        boolean simulatedPlugin = false;
        File simPlugin = null;

        // create a plugin file facsimile if the plugin does not exist in the test environment
        PluginLocator locator = new PluginLocator( gdd );
        try {
            locator.locate( "html" );
        }
        catch ( StopExecutionException soe ) {
            byte[] content = {'a', 'l', 'b'};
            simPlugin = new File( locator.getLocation() );
            try {
                com.google.common.io.Files.write( content, simPlugin );
                System.out.println( "created simulated plugin: " + locator.getLocation() );
            }
            catch( IOException ioe ) {
                fail( "IOException in testFormatSwitch() in ConfigFileTest.java" );
            }
            simulatedPlugin = true;
        }

        // now start the real test

        String[] args = new String[] {
            "input.txt", "input.pdf", "-format", "html"
        };

        clp = new ClParser( args );
        CommandLine cli = clp.getLine();
        assertTrue( cli != null );

        ClProcessor clproc = new ClProcessor( clp, args, gdd );
        clproc.process();

        assertEquals( "html", gdd.sysStrings.get("_FORMAT"));
        assertEquals( "input.pdf", gdd.sysStrings.get("_OUTPUT_FILE"));

        // clean up any simulated plugin
        if( simulatedPlugin ) {
            simPlugin.delete();
        }
    }
}
